package main
import "fmt"
import "unsafe"
const (
	a = "abcd"
	b = len(a)
	//获取字符串byte
	c = unsafe.Sizeof(a)
)

func main() {
	setParm()
	popLeft()
	initArray()
	initPtr()
	initPtrArray()
	initOptPtr()
	initStruct()
	initSlice()
	initGoroutine()
}
func setParm (){
	fmt.Println("变量赋值:")
	f := "Runoob"
	var name =  "zhangzhisong"
	fmt.Println(f)
	fmt.Println(unsafe.Sizeof(name))
	fmt.Println(b)
	fmt.Println(c)
}
//进制左移   3转换二进制:11  左移1位变成110   j= 6     注：<<n==*(2^n)  k照j左移
const (
	i=1<<iota
	j=3<<iota
	k
	l
)
func popLeft()  {
	fmt.Println("进制左移:")
	fmt.Println("i=",i)
	fmt.Println("j=",j)
	fmt.Println("k=",k)
	fmt.Println("l=",l)
}
func initArray()  {
	fmt.Println("初始化数组:")
	var balance = []float32{1000.0, 2.0, 3.4, 7.0, 50.0}
	fmt.Println("balance=",balance[0])
}
func initPtr()  {
	fmt.Println("初始化指针:")
	var a int= 20   /* 声明实际变量 */
	var ip *int        /* 声明指针变量 */

	ip = &a  /* 指针变量的存储地址 */

	fmt.Printf("a 变量的地址是: %x\n", &a  )

	/* 指针变量的存储地址 */
	fmt.Printf("ip 变量储存的指针地址: %x\n", ip )

	/* 使用指针访问值 */
	fmt.Printf("*ip 变量的值: %d\n", *ip )
}
func initPtrArray()  {
	fmt.Println("初始化指针数组:")
	const max int = 3
	a := []int{10,100,200}
	var i int
	var ptr [max]*int;

	for  i = 0; i < max ; i++ {
		ptr[i] = &a[i] /* 整数地址赋值给指针数组 */
	}

	for  i = 0; i < max ; i++ {
		fmt.Printf("a[%d] = %d\n", i,*ptr[i] )
	}
}
func initOptPtr()  {
	fmt.Println("指向指针的指针:")
	var a int = 5
	//把ptr指针 指向ss所在地址
	var ptr *int = &a
	//开辟一个新的指针，指向ptr指针指向的地方
	var pts *int = ptr
	//二级指针，指向一个地址，这个地址存储的是一级指针的地址
	var pto **int = &ptr
	//三级指针，指向一个地址，这个地址存储的是二级指针的地址，二级指针同上
	var pt3 ***int = &pto
	fmt.Println("ptr= ",ptr)
	fmt.Println("ptr= ",*ptr)
	fmt.Println("pts= ",pts)
	fmt.Println("pts= ",*pts)
	fmt.Println("pto= ",pto)
	fmt.Println("pto= ",**pto)
	fmt.Println("pt3= ",pt3)
	fmt.Println("pt3= ",***pt3)
}
type Books struct {
	title string
	author string
	subject string
	book_id int
}
func initStruct()  {
	fmt.Println("初始化结构体:")
	var Book1 Books        /* 声明 Book1 为 Books 类型 */
	var Book2 Books        /* 声明 Book2 为 Books 类型 */

	/* book 1 描述 */
	Book1.title = "Go 语言"
	Book1.author = "www.runoob.com"
	Book1.subject = "Go 语言教程"
	Book1.book_id = 6495407

	/* book 2 描述 */
	Book2.title = "Python 教程"
	Book2.author = "www.runoob.com"
	Book2.subject = "Python 语言教程"
	Book2.book_id = 6495700

	/* 打印 Book1 信息 */
	fmt.Printf( "Book 1 title : %s\n", Book1.title)
	fmt.Printf( "Book 1 author : %s\n", Book1.author)
	fmt.Printf( "Book 1 subject : %s\n", Book1.subject)
	fmt.Printf( "Book 1 book_id : %d\n", Book1.book_id)

	/* 打印 Book2 信息 */
	fmt.Printf( "Book 2 title : %s\n", Book2.title)
	fmt.Printf( "Book 2 author : %s\n", Book2.author)
	fmt.Printf( "Book 2 subject : %s\n", Book2.subject)
	fmt.Printf( "Book 2 book_id : %d\n", Book2.book_id)
}
func initSlice()  {
	fmt.Println("初始化切片:")
	/* 创建切片 */
	numbers := []int{0,1,2,3,4,5,6,7,8}
	printSlice(numbers)

	/* 打印原始切片 */
	fmt.Println("numbers ==", numbers)

	/* 打印子切片从索引1(包含) 到索引4(不包含)*/
	fmt.Println("numbers[1:4] ==", numbers[1:4])

	/* 默认下限为 0*/
	fmt.Println("numbers[:3] ==", numbers[:3])

	/* 默认上限为 len(s)*/
	fmt.Println("numbers[4:] ==", numbers[4:])

	numbers1 := make([]int,0,5)
	printSlice(numbers1)

	/* 打印子切片从索引  0(包含) 到索引 2(不包含) */
	number2 := numbers[:2]
	printSlice(number2)

	/* 打印子切片从索引 2(包含) 到索引 5(不包含) */
	number3 := numbers[2:5]
	printSlice(number3)
}
func printSlice(x []int){
	fmt.Printf("len=%d cap=%d slice=%v\n",len(x),cap(x),x)
}
func initRange()  {
	nums := []int{2, 3, 4}
	sum := 0
	for _, num := range nums {
		sum += num
	}
	fmt.Println("sum:", sum)
}
func initMap()  {
	countryCapitalMap := map[string]string{"France": "Paris", "Italy": "Rome", "Japan": "Tokyo", "India": "New delhi"}
	for country := range countryCapitalMap {
		fmt.Println(country, "首都是", countryCapitalMap [ country ])
	}
}
func sum(s []int, c chan int) {
	sum := 0
	for _, v := range s {
		sum += v
	}
	c <- sum // 把 sum 发送到通道 c
}
func initGoroutine()  {
	fmt.Println("初始化通道:")
	s := []int{7, 2, 8, -9, 4, 0}

	c := make(chan int)
	go sum(s[:len(s)/2], c)
	go sum(s[len(s)/2:], c)
	x, y := <-c, <-c // 从通道 c 中接收
	fmt.Println(x, y, x+y)
	//x:= <-c
	//fmt.Println(x)

	ch := make(chan int, 2)

	// 因为 ch 是带缓冲的通道，我们可以同时发送两个数据
	// 而不用立刻需要去同步读取数据
	ch <- 1
	ch <- 2

	// 获取这两个数据
	fmt.Println(<-ch)
	fmt.Println(<-ch)
}